home *** CD-ROM | disk | FTP | other *** search
/ CD ROM Paradise Collection 4 / CD ROM Paradise Collection 4 1995 Nov.iso / program / swagn_r.zip / NETWORK.SWG / 0021_NOVELL Library.pas < prev    next >
Pascal/Delphi Source File  |  1994-05-26  |  61KB  |  2,133 lines

  1.  
  2. UNIT Novell;
  3. {---------------------------------------------------------------------------}
  4. {                                                                           }
  5. {  This UNIT provides a method of obtaining Novell information from a user  }
  6. {  written program.  This UNIT was tested on an IBM AT running DOS 5.0 &    }
  7. {  using Netware 2.15.  The unit compiled cleanly under Turbo Pascal 6.0    }
  8. {                                                                           }
  9. {  The UNIT has been updated to compile and run under Turbo Pascal for      }
  10. {  Windows.                                                                 }
  11. {                                                                           }
  12. {  *** Tested ok with Netware 386 3.11  Sept/91                             }
  13. {                                                                           }
  14. {  Last Update:   11 Dec 91                                                 }
  15. {                                                                           }
  16. {---------------------------------------------------------------------------}
  17. {                                                                           }
  18. {  Any questions can be directed to:                                        }
  19. {                                                                           }
  20. {  Mark Bramwell                                                            }
  21. {  University of Western Ontario                                            }
  22. {  London, Ontario, N6A 3K7                                                 }
  23. {                                                                           }
  24. {  Phone:  519-473-3618 [work]              519-473-3618 [home]             }
  25. {                                                                           }
  26. {  Bitnet: mark@hamster.business.uwo.ca     Packet: ve3pzr @ ve3gyq         }
  27. {                                                                           }
  28. {  Anonymous FTP Server Internet Address: 129.100.22.100                    }
  29. {                                                                           }
  30. {---------------------------------------------------------------------------}
  31.  
  32. { Any other Novell UNITS gladly accepted. }
  33.  
  34.  
  35. {
  36. mods February 1 1991, Ross Lazarus (rml@extro.ucc.su.AU.OZ)
  37.      var retcodes in procedure getservername, get_broadcast_message,
  38.      verify_object_password comments, password conversion to upper case,
  39.  
  40. Seems to work fine on a Netware 3.00 and on 3.01 servers -
  41. }
  42.  
  43.  
  44. INTERFACE
  45.  
  46. {$IFDEF WINDOWS}
  47. Uses WinDos;
  48. {$ENDIF WINDOWS}
  49.  
  50. {$IFNDEF WINDOWS}
  51. Uses Dos;
  52. {$ENDIF WINDOWS}
  53.  
  54. Const
  55.   Months : Array [1..12] of String[3] = ('JAN','FEB','MAR','APR','MAY','JUN',
  56.                                          'JUL','AUG','SEP','OCT','NOV','DEC');
  57.  
  58.   HEXDIGITS : Array [0..15] of char = '0123456789ABCDEF';
  59.  
  60. Type    byte4 = array [1..4] of byte;
  61.  
  62.         byte6 = array [1..6] of byte;
  63.  
  64. VAR
  65.  
  66. {----------------------------------------------------------------------}
  67. {  The following values can be pulled from an user written application }
  68. {                                                                      }
  69. {  The programmer would first call   GetServerInfo.                    }
  70. {  Then he could   writeln(serverinfo.name)   to print the server name }
  71. {----------------------------------------------------------------------}
  72.  
  73.       ServerInfo    : Record
  74.                      ReturnLength    : Integer;
  75.                      Server          : Packed Array [1..48] of Byte;
  76.                      NetwareVers     : Byte;
  77.                      NetwareSubV     : Byte;
  78.                      ConnectionMax   : array [1..2] of byte;
  79.                      ConnectionUse   : array [1..2] of byte;
  80.                      MaxConVol       : array [1..2] of byte; {}
  81.                      OS_revision     : byte;
  82.                      SFT_level       : byte;
  83.                      TTS_level       : byte;
  84.                      peak_used       : array [1..2] of byte;
  85.                   accounting_version : byte;
  86.                      vap_version     : byte;
  87.                      queuing_version : byte;
  88.                 print_server_version : byte;
  89.              virtual_console_version : byte;
  90.        security_restrictions_version : byte;
  91.         Internetwork_version_version : byte;
  92.                         Undefined    : Packed Array [1..60] of Byte;
  93.                peak_connections_used : integer;
  94.                      Connections_max : integer;
  95.                   Connections_in_use : integer;
  96.                Max_connected_volumes : integer;
  97.                                 name : string;
  98.                    End;
  99.  
  100.  
  101. procedure get_server_lan_driver_information(var _lan_board_number : integer;
  102. { This will return info on what }           var _text1,_text2:string;
  103. { type of network cards are being }         var _network_address : byte4;
  104. { used in the server. }                     var _host_address : byte6;
  105.                                             var _driver_installed,
  106.                                                 _option_number,
  107.                                                 _retcode : integer);
  108.  
  109. procedure GetConnectionInfo(var LogicalStationNo: integer;
  110.                             var name,hex_id:string;
  111.                             var conntype:integer;
  112.                             var datetime:string;
  113.                             var retcode:integer);
  114. { returns username and login date/time when you supply the station number. }
  115.  
  116. procedure clear_connection(connection_number : integer; var retcode :
  117. integer);
  118. { kicks the workstation off the server}
  119.  
  120. procedure GetHexID(var userid,hexid: string;
  121.                    var retcode: integer);
  122. { returns the novell hexid of an username when you supply the username. }
  123.  
  124. procedure GetServerInfo;
  125. { returns various info of the default server }
  126.  
  127. procedure GetUser( var _station: integer;
  128.                    var _username: string;
  129.                    var retcode:integer);
  130. { returns logged-in station username when you supply the station number. }
  131.  
  132. procedure GetNode( var hex_addr: string;
  133.                    var retcode: integer);
  134. { returns your physical network node in hex. }
  135.  
  136. procedure GetStation( var _station: integer;
  137.                       var retcode: integer);
  138. { returns the station number of your workstation }
  139.  
  140. procedure GetServerName(var servername : string;
  141.                         var retcode : integer);
  142.  
  143. { returns the name of the current server }
  144.  
  145. procedure Send_Message_to_Username(username,message : string;
  146.                                    var retcode: integer);
  147. { Sends a novell message to the userid's workstation }
  148.  
  149. procedure Send_Message_to_Station(station:integer;
  150.                                   message : string;
  151.                                   var retcode: integer);
  152. { Sends a message to the workstation station # }
  153.  
  154. procedure Get_Volume_Name(var volume_name: string;
  155.                           volume_number: integer;
  156.                           var retcode:integer);
  157. { Gets the Volume name from Novell network drive }
  158. { Example:  SYS    Note: default drive must be a }
  159. { network drive.                                 }
  160.  
  161. procedure get_realname(var userid:string;
  162.                        var realname:string;
  163.                        var retcode:integer);
  164. { You supply the userid, and it returns the realname as stored by syscon. }
  165. { Example:  userid=mbramwel   realname=Mark Bramwell }
  166.  
  167. procedure get_broadcast_mode(var bmode:integer);
  168.  
  169. procedure set_broadcast_mode(bmode:integer);
  170.  
  171. procedure get_broadcast_message(var bmessage: string;
  172.                                 var retcode : integer);
  173.  
  174. procedure get_server_datetime(var _year,_month,_day,_hour,_min,_sec,_dow:integer);
  175. { pulls from the server the date, time and Day Of Week }
  176.  
  177. procedure set_date_from_server;
  178. { pulls the date from the server and updates the workstation's clock }
  179.  
  180. procedure set_time_from_server;
  181. { pulls the time from the server and updates the workstation's clock }
  182.  
  183. procedure get_server_version(var _version : string);
  184.  
  185. procedure open_message_pipe(var _connection, retcode : integer);
  186.  
  187. procedure close_message_pipe(var _connection, retcode : integer);
  188.  
  189. procedure check_message_pipe(var _connection, retcode : integer);
  190.  
  191. procedure send_personal_message(var _connection : integer; var _message :
  192. string; var retcode : integer);
  193.  
  194. procedure get_personal_message(var _connection : integer; var _message :
  195. string; var retcode : integer);
  196.  
  197. procedure get_drive_connection_id(var drive_number,
  198.                                   server_number : integer);
  199. {pass the drive number - it returns the server number if a network volume}
  200.  
  201. procedure get_file_server_name(var server_number : integer;
  202.                                var server_name : string);
  203.  
  204. procedure get_directory_path(var handle : integer;
  205.                              var pathname : string;
  206.                              var retcode : integer);
  207.  
  208. procedure get_drive_handle_id(var drive_number, handle_number : integer);
  209.  
  210. procedure set_preferred_connection_id(server_num : integer);
  211.  
  212. procedure get_preferred_connection_id(var server_num : integer);
  213.  
  214. procedure set_primary_connection_id(server_num : integer);
  215.  
  216. procedure get_primary_connection_id(var server_num : integer);
  217.  
  218. procedure get_default_connection_id(var server_num : integer);
  219.  
  220. procedure Get_Internet_Address(station : integer;
  221.                                var net_number, node_addr, socket_number :
  222. string;
  223.                                var retcode : integer);
  224.  
  225. procedure login_to_file_server(obj_type:integer; _name,_password : string;var
  226. retcode:integer);
  227.  
  228. procedure logout;
  229.  
  230. procedure logout_from_file_server(var id: integer);
  231.  
  232. procedure down_file_server(flag:integer;var retcode : integer);
  233.  
  234. procedure detach_from_file_server(var id,retcode:integer);
  235.  
  236. procedure disable_file_server_login(var retcode : integer);
  237.  
  238. procedure enable_file_server_login(var retcode : integer);
  239.  
  240. procedure alloc_permanent_directory_handle(var _dir_handle : integer;
  241.                                            var _drive_letter : string;
  242.                                            var _dir_path_name : string;
  243.                                            var _new_dir_handle : integer;
  244.                                            var _effective_rights: byte;
  245.                                            var _retcode : integer);
  246.  
  247. procedure map(var drive_spec:string;
  248.               var _rights:byte;
  249.               var _retcode : integer);
  250.  
  251. procedure scan_object(var last_object: longint;
  252.                       var search_object_type: integer;
  253.                       var search_object : string;
  254.                       var replyid : longint;
  255.                       var replytype : integer; var replyname : string;
  256.                       var replyflag : integer; var replysecurity : byte;
  257.                       var replyproperties : integer; var retcode : integer);
  258.  
  259. procedure verify_object_password(var object_type:integer; var
  260. object_name,password : string; var retcode : integer);
  261.  
  262. {--------------------------------------------------------------------------}
  263. { file locking routines }
  264. {-----------------------}
  265.  
  266. procedure log_file(lock_directive:integer; log_filename: string;
  267. log_timeout:integer; var retcode:integer);
  268.  
  269. procedure clear_file_set;
  270.  
  271. procedure lock_file_set(lock_timeout:integer; var retcode:integer);
  272.  
  273. procedure release_file_set;
  274.  
  275. procedure release_file(log_filename: string; var retcode:integer);
  276.  
  277. procedure clear_file(log_filename: string; var retcode:integer);
  278.  
  279. {--------------------------------------------------------------------------
  280. ---}
  281.  
  282. procedure open_semaphore( _name:string;
  283.                           _initial_value:shortint;
  284.                           var _open_count:integer;
  285.                           var _handle:longint;
  286.                           var retcode:integer);
  287.  
  288. procedure close_semaphore(var _handle:longint; var retcode:integer);
  289.  
  290. procedure examine_semaphore(var _handle:longint; var _value:shortint; var
  291. _count, retcode:integer);
  292.  
  293. procedure signal_semaphore(var _handle:longint; var retcode:integer);
  294.  
  295. procedure wait_on_semaphore(var _handle:longint; _timeout:integer; var
  296. retcode:integer);
  297.  
  298. procedure purge_all_erased_files(var retcode:integer);
  299.  
  300. procedure purge_erased_files(var retcode:integer);
  301. {--------------------------------------------------------------------------
  302. ---}
  303.  
  304.  
  305. IMPLEMENTATION
  306.  
  307. const
  308.      zero = '0';
  309.  
  310. var
  311.    retcode : byte; { return code for all functions }
  312.  
  313. {$IFDEF WINDOWS}
  314.   regs : TRegisters;   { Turbo Pascal for Windows }
  315. {$ENDIF WINDOWS}
  316.  
  317. {$IFNDEF WINDOWS}
  318.   regs : registers;    { Turbo Pascal for Dos }
  319. {$ENDIF WINDOWS}
  320.  
  321. procedure get_volume_name(var volume_name: string; volume_number: integer;
  322.                           var retcode:integer);
  323. {
  324. pulls volume names from default server.  Use set_preferred_connection_id to
  325. set the default server.
  326. retcodes:  0=ok, 1=no volume assigned  98h= # out of range
  327. }
  328.  
  329. VAR
  330.    count,count1  : integer;
  331.  
  332.    requestbuffer : record
  333.       len        : integer;
  334.       func       : byte;
  335.       vol_num    : byte;
  336.       end;
  337.  
  338.     replybuffer  : record
  339.       len        : integer;
  340.       vol_length : byte;
  341.       name       : packed array [1..16] of byte;
  342.       end;
  343.  
  344. begin
  345. With Regs do
  346. begin
  347.   ah := $E2;
  348.   ds := seg(requestbuffer);
  349.   si := ofs(requestbuffer);
  350.   es := seg(replybuffer);
  351.   di := ofs(replybuffer);
  352.  end;
  353.  With requestbuffer do
  354.  begin
  355.   len  := 2;
  356.   func := 6;
  357.   vol_num := volume_number;  {passed from calling program}
  358.  end;
  359.  With replybuffer do
  360.  begin
  361.   len :=  17;
  362.   vol_length := 0;
  363.   for count := 1 to 16 do name[count] := $00;
  364.  end;
  365.  msdos(Regs);
  366.  volume_name := '';
  367.  if replybuffer.vol_length > 0 then
  368.     for count := 1 to replybuffer.vol_length do
  369.         volume_name := volume_name + chr(replybuffer.name[count]);
  370.  retcode := Regs.al;
  371. end;
  372.  
  373. procedure verify_object_password(var object_type:integer; var
  374. object_name,password : string; var retcode : integer);
  375. {
  376. for netware 3.xx remember to have previously (eg in the autoexec file )
  377. set allow unencrypted passwords = on
  378. on the console, otherwise this call always fails !
  379. Note that intruder lockout status is affected by this call !
  380. Netware security isn't that stupid....
  381. Passwords appear to need to be converted to upper case
  382.  
  383. retcode      apparent meaning as far as I can work out....
  384.  
  385. 0            verification of object_name/password combination
  386. 197          account disabled due to intrusion lockout
  387. 214          unencrypted password calls not allowed on this v3+ server
  388. 252          no such object_name on this server
  389. 255          failure to verify object_name/password combination
  390.  
  391. }
  392. var  request_buffer : record
  393.       buffer_length : integer;
  394.         subfunction : byte;
  395.            obj_type : array [1..2] of byte;
  396.     obj_name_length : byte;
  397.            obj_name : array [1..47] of byte;
  398.     password_length : byte;
  399.        obj_password : array [1..127] of byte;
  400.                 end;
  401.  
  402.        reply_buffer : record
  403.       buffer_length : integer;
  404.                 end;
  405.  
  406.               count : integer;
  407.  
  408. begin
  409.      With request_buffer do
  410.      begin
  411.           buffer_length := 179;
  412.           subfunction := $3F;
  413.           obj_type[1] := 0;
  414.           obj_type[2] := object_type;
  415.           obj_name_length := 47;
  416.           for count := 1 to 47 do
  417.               obj_name[count] := $00;
  418.           for count := 1 to length(object_name) do
  419.           obj_name[count] := ord(object_name[count]);
  420.           password_length := length(password);
  421.           for count := 1 to 127 do
  422.               obj_password[count] := $00;
  423.           if password_length > 0 then
  424.              for count := 1 to password_length do
  425.                  obj_password[count] := ord(upcase(password[count]));
  426.        end;
  427.        With reply_buffer do
  428.             buffer_length := 0;
  429.        With regs do
  430.        begin
  431.             Ah := $E3;
  432.             Ds := Seg(Request_Buffer);
  433.             Si := Ofs(Request_Buffer);
  434.             Es := Seg(Reply_Buffer);
  435.             Di := Ofs(Reply_Buffer);
  436.        End;
  437.        msdos(regs);
  438.        retcode := regs.al;
  439. end; { verify_object_password }
  440.  
  441.  
  442.  
  443. procedure scan_object(var last_object: longint; var search_object_type:
  444. integer;
  445.                       var search_object : string; var replyid : longint;
  446.                       var replytype : integer; var replyname : string;
  447.                       var replyflag : integer; var replysecurity : byte;
  448.                       var replyproperties : integer; var retcode : integer);
  449. var
  450.     request_buffer : record
  451.      buffer_length : integer;
  452.        subfunction : byte;
  453.          last_seen : longint;
  454.        search_type : array [1..2] of byte;
  455.        name_length : byte;
  456.        search_name : array [1..47] of byte;
  457.                end;
  458.  
  459.       reply_buffer : record
  460.      buffer_length : integer;
  461.          object_id : longint;
  462.        object_type : array [1..2] of byte;
  463.        object_name : array [1..48] of byte;
  464.        object_flag : byte;
  465.           security : byte;
  466.         properties : byte;
  467.                end;
  468.  
  469.              count : integer;
  470.  
  471. begin
  472. with request_buffer do
  473. begin
  474.  buffer_length := 55;
  475.  subfunction := $37;
  476.  last_seen := last_object;
  477.  if search_object_type = -1 then { -1 = wildcard }
  478.    begin
  479.    search_type[1] := $ff;
  480.    search_type[2] := $ff;
  481.    end else
  482.    begin
  483.    search_type[1] := 0;
  484.    search_type[2] := search_object_type;
  485.    end;
  486. name_length := length(search_object);
  487. for count := 1 to 47 do search_name[count] := $00;
  488. if name_length > 0 then for count := 1 to name_length do
  489.    search_name[count] := ord(upcase(search_object[count]));
  490. end;
  491. With reply_buffer do
  492. begin
  493.  buffer_length := 57;
  494.  object_id:= 0;
  495.  object_type[1] := 0;
  496.  object_type[2] := 0;
  497.  for count := 1 to 48 do object_name[count] := $00;
  498.  object_flag := 0;
  499.  security := 0;
  500.  properties := 0;
  501. end;
  502. With Regs Do Begin
  503.  Ah := $E3;
  504.  Ds := Seg(Request_Buffer);
  505.  Si := Ofs(Request_Buffer);
  506.  Es := Seg(Reply_Buffer);
  507.  Di := Ofs(Reply_Buffer);
  508. End;
  509. msdos(regs);
  510. retcode := regs.al;
  511. With reply_buffer do
  512. begin
  513.  replyflag := object_flag;
  514.  replyproperties := properties;
  515.  replysecurity := security;
  516.  replytype := object_type[2];
  517.  replyid := object_id;
  518. end;
  519. count := 1;
  520. replyname := '';
  521. While (count <= 48)  and (reply_buffer.Object_Name[count] <> 0) Do Begin
  522.     replyName := replyname + Chr(reply_buffer.Object_name[count]);
  523.     count := count + 1;
  524.     End { while };
  525. end;
  526.  
  527.  
  528. procedure alloc_permanent_directory_handle
  529.   (var _dir_handle : integer; var _drive_letter : string;
  530.    var _dir_path_name : string; var _new_dir_handle : integer;
  531.    var _effective_rights: byte; var _retcode : integer);
  532.  
  533. var request_buffer : record
  534.      buffer_length : integer;
  535.        subfunction : byte;
  536.         dir_handle : byte;
  537.       drive_letter : byte;
  538.    dir_path_length : byte;
  539.      dir_path_name : packed array [1..255] of byte;
  540.                end;
  541.  
  542.       reply_buffer : record
  543.      buffer_length : integer;
  544.     new_dir_handle : byte;
  545.   effective_rights : byte;
  546.                end;
  547.  
  548.   count : integer;
  549.  
  550. begin
  551. With request_buffer do
  552. begin
  553.  buffer_length := 259;
  554.  subfunction := $12;
  555.  dir_handle := _dir_handle;
  556.  drive_letter := ord(upcase(_drive_letter[1]));
  557.  dir_path_length := length(_dir_path_name);
  558.  for count := 1 to 255 do dir_path_name[count] := $0;
  559.  if dir_path_length > 0 then for count := 1 to dir_path_length do
  560.     dir_path_name[count] := ord(upcase(_dir_path_name[count]));
  561. end;
  562. With reply_buffer do
  563. begin
  564.  buffer_length := 2;
  565.  new_dir_handle := 0;
  566.  effective_rights := 0;
  567. end;
  568. With Regs Do Begin
  569.  Ah := $E2;
  570.  Ds := Seg(Request_Buffer);
  571.  Si := Ofs(Request_Buffer);
  572.  Es := Seg(Reply_Buffer);
  573.  Di := Ofs(Reply_Buffer);
  574. End;
  575. msdos(regs);
  576. _retcode := regs.al;
  577. _effective_rights := $0;
  578. _new_dir_handle := $0;
  579. if _retcode = 0 then
  580. begin
  581.  _effective_rights := reply_buffer.effective_rights;
  582.  _new_dir_handle := reply_buffer.new_dir_handle;
  583. end;
  584. end;
  585.  
  586. procedure map(var drive_spec:string; var _rights:byte; var _retcode :
  587. integer);
  588. var
  589.     dir_handle : integer;
  590.      path_name : string;
  591.         rights : byte;
  592.   drive_number : integer;
  593.   drive_letter : string;
  594.     new_handle : integer;
  595.        retcode : integer;
  596.  
  597. begin
  598.  {first thing is we strip leading and trailing blanks}
  599.  while drive_spec[1]=' ' do  drive_spec :=
  600. copy(drive_spec,2,length(drive_spec));
  601.  while drive_spec[length(drive_spec)]=' ' do  drive_spec :=
  602. copy(drive_spec,1,length(drive_spec)-1);
  603.  drive_number := ord(upcase(drive_spec[1]))-65;
  604.  drive_letter := upcase(drive_spec[1]);
  605.  path_name := copy(drive_spec,4,length(drive_spec));
  606.  get_drive_handle_id(drive_number,dir_handle);
  607.  alloc_permanent_directory_handle(dir_handle,drive_letter,path_name,new_handle,
  608.  rights,retcode);
  609.  _retcode := retcode;
  610.  _rights := rights;
  611. end;
  612.  
  613.  
  614.  
  615.  
  616. procedure down_file_server(flag:integer;var retcode : integer);
  617. var
  618.  
  619. request_buffer : record
  620.  buffer_length : integer;
  621.    subfunction : byte;
  622.      down_flag : byte;
  623.            end;
  624.  
  625.   reply_buffer : record
  626.  buffer_length : integer;
  627.            end;
  628.  
  629. begin
  630. With request_buffer do
  631. begin
  632.  buffer_length := 2;
  633.  subfunction := $D3;
  634.  down_flag := flag;
  635. end;
  636. reply_buffer.buffer_length := 0;
  637. With Regs Do Begin
  638.  Ah := $E3;
  639.  Ds := Seg(Request_Buffer);
  640.  Si := Ofs(Request_Buffer);
  641.  Es := Seg(Reply_Buffer);
  642.  Di := Ofs(Reply_Buffer);
  643. End;
  644. msdos(regs);
  645. retcode := regs.al;
  646. end;
  647.  
  648.  
  649. procedure set_preferred_connection_id(server_num : integer);
  650. begin
  651.  regs.ah := $F0;
  652.  regs.al := $00;
  653.  regs.ds := 0;
  654.  regs.es := 0;
  655.  regs.dl := server_num;
  656.  msdos(regs);
  657. end;
  658.  
  659. procedure set_primary_connection_id(server_num : integer);
  660. begin
  661.  regs.ah := $F0;
  662.  regs.al := $04;
  663.  regs.ds := 0;
  664.  regs.es := 0;
  665.  regs.dl := server_num;
  666.  msdos(regs);
  667. end;
  668.  
  669. procedure get_primary_connection_id(var server_num : integer);
  670. begin
  671.  regs.ah := $F0;
  672.  regs.al := $05;
  673.  regs.es := 0;
  674.  regs.ds := 0;
  675.  msdos(regs);
  676.  server_num := regs.al;
  677. end;
  678.  
  679. procedure get_default_connection_id(var server_num : integer);
  680. begin
  681.  regs.ah := $F0;
  682.  regs.al := $02;
  683.  regs.es := 0;
  684.  regs.ds := 0;
  685.  msdos(regs);
  686.  server_num := regs.al;
  687. end;
  688.  
  689. procedure get_preferred_connection_id(var server_num : integer);
  690. begin
  691.  regs.ah := $F0;
  692.  regs.al := $02;
  693.  regs.ds := 0;
  694.  regs.es := 0;
  695.  msdos(regs);
  696.  server_num := regs.al;
  697. end;
  698.  
  699.  
  700. procedure get_drive_connection_id(var drive_number, server_number : integer);
  701. var
  702.  
  703.  drive_table : array [1..32] of byte;
  704.        count : integer;
  705.            p : ^byte;
  706.  
  707. begin
  708.   regs.ah := $EF;
  709.   regs.al := $02;
  710.   regs.es := 0;
  711.   regs.ds := 0;
  712.   msdos(regs);
  713.   p := ptr(regs.es, regs.si);
  714.   move(p^,drive_table,32);
  715.   if ((drive_number < 0) or (drive_number > 32))  then drive_number := 1;
  716.   server_number := drive_table[drive_number];
  717. end;
  718.  
  719. procedure get_drive_handle_id(var drive_number, handle_number : integer);
  720. var
  721.  drive_table : array [1..32] of byte;
  722.        count : integer;
  723.            p : ^byte;
  724.  
  725. begin
  726.   regs.ah := $EF;
  727.   regs.al := $00;
  728.   regs.ds := 0;
  729.   regs.es := 0;
  730.   msdos(regs);
  731.   p := ptr(regs.es, regs.si);
  732.   move(p^,drive_table,32);
  733.   if ((drive_number < 0) or (drive_number > 32))  then drive_number := 1;
  734.   handle_number := drive_table[drive_number];
  735. end;
  736.  
  737.  
  738. procedure get_file_server_name(var server_number : integer; var server_name :
  739. string);
  740. var
  741.   name_table : array [1..8*48] of byte;
  742.       server : array [1..8] of string;
  743.        count : integer;
  744.       count2 : integer;
  745.            p : ^byte;
  746.      no_more : integer;
  747.  
  748. begin
  749.   regs.ah := $EF;
  750.   regs.al := $04;
  751.   regs.ds := 0;
  752.   regs.es := 0;
  753.   msdos(regs);
  754.   no_more := 0;
  755.   p := ptr(regs.es, regs.si);
  756.   move(p^,name_table,8*48);
  757.   for count := 1 to 8 do server[count] := '';
  758.   for count := 0 to 7 do
  759.   begin
  760.     no_more := 0;
  761.     for count2 := (count*48)+1 to (count*48)+48 do if name_table[count2] <>
  762. $00
  763.         then
  764.         begin
  765.         if no_more=0 then server[count+1] := server[count+1] +
  766. chr(name_table[count2]);
  767.         end else no_more:=1; {scan until 00h is found}
  768.   end;
  769.   if ((server_number<1) or (server_number>8)) then server_number := 1;
  770.   server_name := server[server_number];
  771. end;
  772.  
  773. procedure disable_file_server_login(var retcode : integer);
  774. var  request_buffer : record
  775.       buffer_length : integer;
  776.         subfunction : byte
  777.                 end;
  778.  
  779.   reply_buffer : record
  780.  buffer_length : integer;
  781.            end;
  782.  
  783. begin
  784.   With Regs Do Begin
  785.     Ah := $E3;
  786.     Ds := Seg(Request_Buffer);
  787.     Si := Ofs(Request_Buffer);
  788.     Es := Seg(Reply_Buffer);
  789.     Di := Ofs(Reply_Buffer);
  790.   End;
  791.   With request_buffer do
  792.    begin
  793.    buffer_length := 1;
  794.    subfunction := $CB;
  795.    end;
  796.  reply_buffer.buffer_length := 0;
  797.  msdos(regs);
  798.  retcode := regs.al;
  799. end;
  800.  
  801. procedure enable_file_server_login(var retcode : integer);
  802. var request_buffer : record
  803.      buffer_length : integer;
  804.        subfunction : byte
  805.                end;
  806.  
  807.   reply_buffer : record
  808.  buffer_length : integer;
  809.            end;
  810.  
  811. begin
  812.   With Regs Do Begin
  813.     Ah := $E3;
  814.     Ds := Seg(Request_Buffer);
  815.     Si := Ofs(Request_Buffer);
  816.     Es := Seg(Reply_Buffer);
  817.     Di := Ofs(Reply_Buffer);
  818.   End;
  819.   With request_buffer do
  820.    begin
  821.    buffer_length := 1;
  822.    subfunction := $CC;
  823.    end;
  824.  reply_buffer.buffer_length := 0;
  825.  msdos(regs);
  826.  retcode := regs.al;
  827. end;
  828.  
  829.  
  830. procedure get_directory_path(var handle : integer; var pathname : string; var
  831. retcode : integer);
  832. var count : integer;
  833.  
  834.    request_buffer : record
  835.               len : integer;
  836.       subfunction : byte;
  837.        dir_handle : byte;
  838.               end;
  839.  
  840.      reply_buffer : record
  841.               len : integer;
  842.          path_len : byte;
  843.         path_name : array [1..255] of byte;
  844.               end;
  845.  
  846. begin
  847.   With Regs Do Begin
  848.     Ah := $e2;
  849.     Ds := Seg(Request_Buffer);
  850.     Si := Ofs(Request_Buffer);
  851.     Es := Seg(Reply_Buffer);
  852.     Di := Ofs(Reply_Buffer);
  853.   End;
  854.   With request_buffer do
  855.    begin
  856.    len := 2;
  857.    subfunction := $01;
  858.    dir_handle := handle;
  859.    end;
  860.   With reply_buffer do
  861.    begin
  862.    len := 256;
  863.    path_len := 0;
  864.    for count := 1 to 255 do path_name[count] := $00;
  865.    end;
  866.   msdos(regs);
  867.   retcode := regs.al;
  868.   pathname := '';
  869.   if reply_buffer.path_len > 0 then for count := 1 to reply_buffer.path_len do
  870.      pathname := pathname + chr(reply_buffer.path_name[count]);
  871. end;
  872.  
  873. procedure detach_from_file_server(var id,retcode:integer);
  874. begin
  875.  regs.ah := $F1;
  876.  regs.al := $01;
  877.  regs.dl := id;
  878.  msdos(regs);
  879.  retcode := regs.al;
  880. end;
  881.  
  882.  
  883. procedure getstation( var _station: integer; var retcode: integer);
  884. begin
  885.    With Regs do
  886.    begin
  887.     ah := $DC;
  888.     ds := 0;
  889.     si := 0;
  890.    end;
  891.    MsDos( Regs );
  892.    _station := Regs.al;
  893.    retcode := 0;
  894.    end;
  895.  
  896.  
  897. procedure GetHexID( var userid,hexid: string; var retcode: integer);
  898. var
  899.     i,x           : integer;
  900.     hex_id        : string;
  901.     requestbuffer : record
  902.       len      : integer;
  903.       func     : byte;
  904.       conntype : packed array [1..2] of byte;
  905.       name_len : byte;
  906.       name     : packed array [1..47] of char;
  907.       end;
  908.     replybuffer   : record
  909.       len      : integer;
  910.       uniqueid1: packed array [1..2] of byte;
  911.       uniqueid2: packed array [1..2] of byte;
  912.       conntype : word;
  913.       name     : packed array [1..48] of byte;
  914.       end;
  915.  
  916. begin
  917.   regs.ah := $E3;
  918.   requestbuffer.func := $35;
  919.   regs.ds := seg(requestbuffer);
  920.   regs.si := ofs(requestbuffer);
  921.   regs.es := seg(replybuffer);
  922.   regs.di := ofs(replybuffer);
  923.   requestbuffer.len := 52;
  924.   replybuffer.len := 55;
  925.   requestbuffer.name_len := length(userid);
  926.   for i := 1 to length(userid) do requestbuffer.name[i] := userid[i];
  927.   requestbuffer.conntype[2] := $1;
  928.   requestbuffer.conntype[1] := $0;
  929.   replybuffer.conntype := 1;
  930.   msdos(regs);
  931.   retcode := regs.al;   {
  932.   if retcode = $96 then writeln('Server out of memory');
  933.   if retcode = $EF then writeln('Invalid name');
  934.   if retcode = $F0 then writeln('Wildcard not allowed');
  935.   if retcode = $FC then writeln('No such object *',userid,'*');
  936.   if retcode = $FE then writeln('Server bindery locked');
  937.   if retcode = $FF then writeln('Bindery failure'); }
  938.   hex_id := '';
  939.   if retcode = 0 then
  940.   begin
  941.    hex_id := hexdigits[replybuffer.uniqueid1[1] shr 4];
  942.    hex_id := hex_id + hexdigits[replybuffer.uniqueid1[1] and $0F];
  943.    hex_id := hex_id + hexdigits[replybuffer.uniqueid1[2] shr 4];
  944.    hex_id := hex_id + hexdigits[replybuffer.uniqueid1[2] and $0F];
  945.    hex_id := hex_id + hexdigits[replybuffer.uniqueid2[1] shr 4];
  946.    hex_id := hex_id + hexdigits[replybuffer.uniqueid2[1] and $0F];
  947.    hex_id := hex_id + hexdigits[replybuffer.uniqueid2[2] shr 4];
  948.    hex_id := hex_id + hexdigits[replybuffer.uniqueid2[2] and $0F];
  949.    { Now we chop off leading zeros }
  950.    while hex_id[1] = '0' do hex_id := copy(hex_id,2,length(hex_id));
  951.   end;
  952.    hexid := hex_id;
  953. end;
  954.  
  955.  
  956. Procedure GetConnectionInfo
  957. (Var LogicalStationNo: Integer; Var Name: String; Var HEX_ID: String;
  958.  Var ConnType : Integer; Var DateTime : String; Var retcode:integer);
  959.  
  960. Var
  961.   I,X            : Integer;
  962.   RequestBuffer  : Record
  963.                      PacketLength : Integer;
  964.                      FunctionVal  : Byte;
  965.                      ConnectionNo : Byte;
  966.                    End;
  967.   ReplyBuffer    : Record
  968.                      ReturnLength : Integer;
  969.                      UniqueID1    : Packed Array [1..2] of byte;
  970.                      UniqueID2    : Packed Array [1..2] of byte;
  971.                      NWConnType   : Packed Array [1..2] of byte;
  972.                      ObjectName   : Packed Array [1..48] of Byte;
  973.                      LoginTime    : Packed Array [1..8] of Byte;
  974.                    End;
  975.   Month          : String[3];
  976.   Year,
  977.   Day,
  978.   Hour,
  979.   Minute         : String[2];
  980.  
  981. Begin
  982.   With RequestBuffer Do Begin
  983.     PacketLength := 2;
  984.     FunctionVal := 22;  { 22 = Get Station Info }
  985.     ConnectionNo := LogicalStationNo;
  986.   End;
  987.   ReplyBuffer.ReturnLength := 62;
  988.   With Regs Do Begin
  989.     Ah := $e3;
  990.     ds := 0;
  991.     es := 0;
  992.     Ds := Seg(RequestBuffer);
  993.     Si := Ofs(RequestBuffer);
  994.     Es := Seg(ReplyBuffer);
  995.     Di := Ofs(ReplyBuffer);
  996.   End;
  997.   MsDos(Regs);
  998.   retcode := regs.al;
  999.   name := '';
  1000.   hex_id := hexdigits[replybuffer.uniqueid1[1] shr 4];
  1001.   hex_id := hex_id + hexdigits[replybuffer.uniqueid1[1] and $0F];
  1002.   hex_id := hex_id + hexdigits[replybuffer.uniqueid1[2] shr 4];
  1003.   hex_id := hex_id + hexdigits[replybuffer.uniqueid1[2] and $0F];
  1004.   hex_id := hex_id + hexdigits[replybuffer.uniqueid2[1] shr 4];
  1005.   hex_id := hex_id + hexdigits[replybuffer.uniqueid2[1] and $0F];
  1006.   hex_id := hex_id + hexdigits[replybuffer.uniqueid2[2] shr 4];
  1007.   hex_id := hex_id + hexdigits[replybuffer.uniqueid2[2] and $0F];
  1008.   { Now we chop off leading zeros }
  1009.     while ( (hex_id[1]='0') and (length(hex_id) > 1) )
  1010.              do hex_id := copy(hex_id,2,length(hex_id));
  1011.   ConnType := replybuffer.nwconntype[2];
  1012.   datetime := '';
  1013.   If hex_id <> '0' Then Begin {Grab username}
  1014.     With ReplyBuffer Do Begin
  1015.       I := 1;
  1016.       While (I <= 48)  and (ObjectName[I] <> 0) Do
  1017.         Begin
  1018.         Name[I] := Chr(Objectname[I]);
  1019.         I := I + 1;
  1020.         End { while };
  1021.      Name[0] := Chr(I - 1);
  1022.    End; {With} End; {if}
  1023.    If hex_id <> '0' then With replybuffer do {Grab login time}
  1024.    begin
  1025.      Str(LoginTime[1]:2,Year);
  1026.      Month := Months[LoginTime[2]];
  1027.      Str(LoginTime[3]:2,Day);
  1028.      Str(LoginTime[4]:2,Hour);
  1029.      Str(LoginTime[5]:2,Minute);
  1030.      If Day[1] = ' ' Then Day[1] := '0';
  1031.      If Hour[1] = ' ' Then Hour[1] := '0';
  1032.      If Minute[1] = ' ' Then Minute[1] := '0';
  1033.      DateTime := Day+'-'+Month+'-'+Year+' ' + Hour + ':' + Minute;
  1034.      End;
  1035. End { GetConnectInfo };
  1036.  
  1037. procedure login_to_file_server(obj_type:integer;_name,_password : string;var
  1038. retcode:integer);
  1039. var   request_buffer : record
  1040.             B_length : integer;
  1041.          subfunction : byte;
  1042.               o_type : packed array [1..2] of byte;
  1043.          name_length : byte;
  1044.             obj_name : packed array [1..47] of byte;
  1045.      password_length : byte;
  1046.             password : packed array [1..27] of byte;
  1047.                  end;
  1048.  
  1049.         reply_buffer : record
  1050.             R_length : integer;
  1051.                  end;
  1052.  
  1053.                count : integer;
  1054.  
  1055. begin
  1056. With request_buffer do
  1057. begin
  1058.  B_length := 79;
  1059.  subfunction := $14;
  1060.  o_type[1] := 0;
  1061.  o_type[2] := obj_type;
  1062.  for count := 1 to 47 do obj_name[count] := $0;
  1063.  for count := 1 to 27 do password[count] := $0;
  1064.  if length(_name) > 0 then
  1065.     for count := 1 to length(_name) do
  1066. obj_name[count]:=ord(upcase(_name[count]));
  1067.  if length(_password) > 0 then
  1068.     for count := 1 to length(_password) do
  1069. password[count]:=ord(upcase(_password[count]));
  1070.  {set to full length of field}
  1071.  name_length := 47;
  1072.  password_length := 27;
  1073. end;
  1074. With reply_buffer do
  1075. begin
  1076.  R_length := 0;
  1077. end;
  1078.   With Regs Do Begin
  1079.     Ah := $e3;
  1080.     Ds := Seg(Request_Buffer);
  1081.     Si := Ofs(Request_Buffer);
  1082.     Es := Seg(reply_buffer);
  1083.     Di := Ofs(reply_buffer);
  1084.   End;
  1085.   MsDos(Regs);
  1086.   retcode := regs.al
  1087. end;
  1088.  
  1089. procedure logout;
  1090. {logout from all file servers}
  1091. begin
  1092.  regs.ah := $D7;
  1093.  msdos(regs);
  1094. end;
  1095.  
  1096. procedure logout_from_file_server(var id: integer);
  1097. {logout from one file server}
  1098. begin
  1099.  regs.ah := $F1;
  1100.  regs.al := $02;
  1101.  regs.dl := id;
  1102.  msdos(regs);
  1103. end;
  1104.  
  1105.  
  1106.  
  1107.  
  1108. procedure send_message_to_username(username,message : string; var retcode:
  1109. integer);
  1110. VAR
  1111.    count1     : byte;
  1112.    userid     : string;
  1113.    stationid  : integer;
  1114.    ret_code   : integer;
  1115.  
  1116. begin
  1117.    ret_code := 1;
  1118.    for count1:= 1 to length(username) do
  1119.        username[count1]:=upcase(username[count1]); { Convert to upper case }
  1120.    getserverinfo;
  1121.    for count1:= 1 to serverinfo.connections_max do
  1122.    begin
  1123.      stationid := count1;
  1124.      getuser( stationid, userid, retcode);
  1125.       if userid = username then
  1126.         begin
  1127.         ret_code := 0;
  1128.         send_message_to_station(stationid, message, retcode);
  1129.       end;
  1130.      end; { end of count }
  1131.      retcode := ret_code;
  1132.      { retcode = 0 if sent,  1 if userid not found }
  1133. end; { end of procedure }
  1134.  
  1135.  
  1136. Procedure GetServerInfo;
  1137. Var
  1138.   RequestBuffer  : Record
  1139.                      PacketLength : Integer;
  1140.                      FunctionVal  : Byte;
  1141.                    End;
  1142.   I              : Integer;
  1143.  
  1144. Begin
  1145.   With RequestBuffer Do Begin
  1146.     PacketLength := 1;
  1147.     FunctionVal := 17;  { 17 = Get Server Info }
  1148.   End;
  1149.   ServerInfo.ReturnLength := 128;
  1150.   With Regs Do Begin
  1151.     Ah := $e3;
  1152.     Ds := Seg(RequestBuffer);
  1153.     Si := Ofs(RequestBuffer);
  1154.     Es := Seg(ServerInfo);
  1155.     Di := Ofs(ServerInfo);
  1156.   End;
  1157.   MsDos(Regs);
  1158.   With serverinfo do
  1159.   begin
  1160.    connections_max := connectionmax[1]*256 + connectionmax[2];
  1161.    connections_in_use := connectionuse[1]*256 + connectionuse[2];
  1162.    max_connected_volumes := maxconvol[1]*256 + maxconvol[2];
  1163.    peak_connections_used := peak_used[1]*256 + peak_used[2];
  1164.    name := '';
  1165.    i := 1;
  1166.    while ((server[i] <> 0) and (i<>48)) do
  1167.     begin
  1168.     name := name + chr(server[i]);
  1169.     i := i + 1;
  1170.     end;
  1171.    end;
  1172. End;
  1173.  
  1174. procedure GetServerName(var servername : string; var retcode : integer);
  1175. {-----------------------------------------------------------------}
  1176. { This routine returns the same as GetServerInfo.  This routine   }
  1177. { was kept to maintain compatibility with the older  novell unit. }
  1178. {-----------------------------------------------------------------}
  1179. begin
  1180.   getserverinfo;
  1181.   servername := serverinfo.name;
  1182.   retcode := 0;
  1183.   end;
  1184.  
  1185. procedure send_message_to_station(station:integer; message : string; var retcode : integer);
  1186. VAR
  1187.    req_buffer : record
  1188.    buffer_len : integer;
  1189.    subfunction: byte;
  1190.       c_count : byte;
  1191.        c_list : byte;
  1192.    msg_length : byte;
  1193.           msg : packed array [1..55] of byte;
  1194.           end;
  1195.  
  1196.    rep_buffer : record
  1197.    buffer_len : integer;
  1198.       c_count : byte;
  1199.        r_list : byte;
  1200.           end;
  1201.  
  1202.    count1     : integer;
  1203.  
  1204. begin
  1205.         if length(message) > 55 then message:=copy(message,1,55);
  1206.         With Regs do
  1207.         begin
  1208.          ah := $E1;
  1209.          ds:=seg(req_buffer);
  1210.          si:=ofs(req_buffer);
  1211.          es:=seg(rep_buffer);
  1212.          di:=ofs(rep_buffer);
  1213.         End;
  1214.         With req_buffer do
  1215.         begin
  1216.          buffer_len := 59;
  1217.          subfunction := 00;
  1218.          c_count := 1;
  1219.          c_list := station;
  1220.          for count1:= 1 to 55 do msg[count1]:= $00; { zero the buffer }
  1221.          msg_length := length(message); { message length }
  1222.          for count1:= 1 to length(message) do
  1223. msg[count1]:=ord(message[count1]);
  1224.         End;
  1225.         With rep_buffer do
  1226.         begin
  1227.          buffer_len := 2;
  1228.          c_count := 1;
  1229.          r_list := 0;
  1230.         End;
  1231.         msdos( Regs );
  1232.         retcode:= rep_buffer.r_list;
  1233.    end;
  1234.  
  1235.  
  1236. procedure getuser( var _station: integer; var  _username: string; var retcode:
  1237. integer);
  1238. {This procedure provides a shorter method of obtaining just the USERID.}
  1239. var
  1240.      gu_hexid : string;
  1241.   gu_conntype : integer;
  1242.   gu_datetime : string;
  1243.  
  1244. begin
  1245.   getconnectioninfo(_station,_username,gu_hexid,gu_conntype,gu_datetime,retcode);
  1246. end;
  1247.  
  1248.  
  1249. PROCEDURE GetNode( var hex_addr: string; var retcode: integer );
  1250. { get the physical station address }
  1251.  
  1252. Const
  1253.    Hex_Set  :packed array[0..15] of char = '0123456789ABCDEF';
  1254.  
  1255. Begin { GetNode }
  1256.    {Get the physical address from the Network Card}
  1257.    Regs.Ah := $EE;
  1258.    regs.ds := 0;
  1259.    regs.es := 0;
  1260.    MsDos(Regs);
  1261.    hex_addr := '';
  1262.    hex_addr := hex_addr + hex_set[(regs.ch shr 4)];
  1263.    hex_addr := hex_addr + hex_set[(regs.ch and $0f)];
  1264.    hex_addr := hex_addr + hex_set[(regs.cl shr 4) ];
  1265.    hex_addr := hex_addr + hex_set[(regs.cl and $0f)];
  1266.    hex_addr := hex_addr + hex_set[(regs.bh shr 4)];
  1267.    hex_addr := hex_addr + hex_set[(regs.bh and $0f)];
  1268.    hex_addr := hex_addr + hex_set[(regs.bl shr 4)];
  1269.    hex_addr := hex_addr + hex_set[(regs.bl and $0f)];
  1270.    hex_addr := hex_addr + hex_set[(regs.ah shr 4)];
  1271.    hex_addr := hex_addr + hex_set[(regs.ah and $0f)];
  1272.    hex_addr := hex_addr + hex_set[(regs.al shr 4)];
  1273.    hex_addr := hex_addr + hex_set[(regs.al and $0f)];
  1274.    retcode := 0;
  1275. End; { Getnode }
  1276.  
  1277.  
  1278. PROCEDURE Get_Internet_Address(station : integer; var net_number, node_addr,
  1279. socket_number : string; var retcode : integer);
  1280.  
  1281.  
  1282. Const
  1283.    Hex_Set  :packed array[0..15] of char = '0123456789ABCDEF';
  1284.  
  1285. Var   Request_buffer : record
  1286.               length : integer;
  1287.          subfunction : byte;
  1288.           connection : byte;
  1289.                  end;
  1290.  
  1291.     Reply_Buffer : record
  1292.           length : integer;
  1293.          network : array [1..4] of byte;
  1294.             node : array [1..6] of byte;
  1295.           socket : array [1..2] of byte;
  1296.              end;
  1297.  
  1298.            count : integer;
  1299.       _node_addr : string;
  1300.   _socket_number : string;
  1301.      _net_number : string;
  1302.  
  1303. begin
  1304.  With Regs do
  1305.  begin
  1306.   ah := $E3;
  1307.   ds:=seg(request_buffer);
  1308.   si:=ofs(request_buffer);
  1309.   es:=seg(reply_buffer);
  1310.   di:=ofs(reply_buffer);
  1311.  End;
  1312.  With request_buffer do
  1313.  begin
  1314.   length := 2;
  1315.   subfunction := $13;
  1316.   connection := station;
  1317.  end;
  1318.  With reply_buffer do
  1319.  begin
  1320.   length := 12;
  1321.   for count := 1 to 4 do network[count] := 0;
  1322.   for count := 1 to 6 do node[count] := 0;
  1323.   for count := 1 to 2 do socket[count] := 0;
  1324.  end;
  1325.  msdos(regs);
  1326.  retcode := regs.al;
  1327.  _net_number := '';
  1328.  _node_addr := '';
  1329.  _socket_number := '';
  1330.  if retcode = 0 then
  1331.  begin
  1332.  for count := 1 to 4 do
  1333.      begin
  1334.      _net_number := _net_number + hex_set[ (reply_buffer.network[count] shr 4)
  1335. ];
  1336.      _net_number := _net_number + hex_set[ (reply_buffer.network[count] and
  1337. $0F) ];
  1338.      end;
  1339.  for count := 1 to 6 do
  1340.      begin
  1341.      _node_addr := _node_addr + (hex_set[ (reply_buffer.node[count] shr 4) ]);
  1342.      _node_addr := _node_addr + (hex_set[ (reply_buffer.node[count] and $0F)
  1343. ]);
  1344.      end;
  1345.  for count := 1 to 2 do
  1346.      begin
  1347.      _socket_number := _socket_number + (hex_set[ (reply_buffer.socket[count]
  1348. shr 4) ]);
  1349.      _socket_number := _socket_number + (hex_set[ (reply_buffer.socket[count]
  1350. and $0F) ]);
  1351.      end;
  1352.  end; {end of retcode=0}
  1353.  net_number := _net_number;
  1354.  node_addr := _node_addr;
  1355.  socket_number := _socket_number;
  1356.  end;
  1357.  
  1358. procedure get_realname(var userid,realname:string; var retcode:integer);
  1359. var
  1360.     requestbuffer : record
  1361.     buffer_length : array [1..2] of byte;
  1362.       subfunction : byte;
  1363.       object_type : array [1..2] of byte;
  1364.     object_length : byte;
  1365.       object_name : array [1..47] of byte;
  1366.           segment : byte;
  1367.   property_length : byte;
  1368.     property_name : array [1..14] of byte;
  1369.     end;
  1370.  
  1371.       replybuffer : record
  1372.     buffer_length : array [1..2] of byte;
  1373.    property_value : array [1..128] of byte;
  1374.     more_segments : byte;
  1375.    property_flags : byte;
  1376.    end;
  1377.  
  1378.    count    : integer;
  1379.    id       : string;
  1380.    fullname : string;
  1381.  
  1382. begin
  1383.   id := 'IDENTIFICATION';
  1384.   With requestbuffer do begin
  1385.      buffer_length[2] := 0;
  1386.      buffer_length[1] := 69;
  1387.      subfunction  := $3d;
  1388.      object_type[1]:= 0;
  1389.      object_type[2]:= 01;
  1390.      segment := 1;
  1391.      object_length := 47;
  1392.      property_length := length(id);
  1393.      for count := 1 to 47 do object_name[count] := $0;
  1394.      for count := 1 to length(userid) do object_name[count] :=
  1395. ord(userid[count]);
  1396.      for count := 1 to 14 do property_name[count] := $0;
  1397.      for count := 1 to length(id) do property_name[count] := ord(id[count]);
  1398.      end;
  1399.   With replybuffer do begin
  1400.      buffer_length[1] := 130;
  1401.      buffer_length[2] := 0;
  1402.      for count := 1 to 128 do property_value[count] := $0;
  1403.      more_segments := 1;
  1404.      property_flags := 0;
  1405.      end;
  1406.   With Regs do begin
  1407.      Ah := $e3;
  1408.      Ds := Seg(requestbuffer);
  1409.      Si := Ofs(requestbuffer);
  1410.      Es := Seg(replybuffer);
  1411.      Di := Ofs(replybuffer);
  1412.      end;
  1413.   MSDOS(Regs);
  1414.   retcode := Regs.al;
  1415.   fullname := '';
  1416.   count := 1;
  1417.   if replybuffer.property_value[1] <> 0 then
  1418.   repeat
  1419.    begin
  1420.    if replybuffer.property_value[count]<>0
  1421.       then fullname := fullname + chr(replybuffer.property_value[count]);
  1422.    count := count + 1;
  1423.    end;
  1424.    until ((count=128) or (replybuffer.property_value[count]=0));
  1425.   {if regs.al = $96 then writeln('server out of memory');
  1426.   if regs.al = $ec then writeln('no such segment');
  1427.   if regs.al = $f0 then writeln('wilcard not allowed');
  1428.   if regs.al = $f1 then writeln('invalid bindery security');
  1429.   if regs.al = $f9 then writeln('no property read priv');
  1430.   if regs.al = $fb then writeln('no such property');
  1431.   if regs.al = $fc then writeln('no such object');}
  1432.   if retcode=0 then realname := fullname else realname:='';
  1433. end;
  1434.  
  1435. procedure get_broadcast_mode(var bmode:integer);
  1436. begin
  1437.  regs.ah := $de;
  1438.  regs.dl := $04;
  1439.  msdos(regs);
  1440.  bmode := regs.al;
  1441. end;
  1442.  
  1443. procedure set_broadcast_mode(bmode:integer);
  1444. begin
  1445.  if ((bmode > 3) or (bmode < 0)) then bmode := 0;
  1446.  regs.ah := $de;
  1447.  regs.dl := bmode;
  1448.  msdos(regs);
  1449.  bmode := regs.al;
  1450. end;
  1451.  
  1452. procedure get_broadcast_message(var bmessage: string; var retcode : integer);
  1453. var requestbuffer : record
  1454.      bufferlength : array [1..2] of byte;
  1455.       subfunction : byte;
  1456.       end;
  1457.  
  1458.       replybuffer : record
  1459.      bufferlength : array [1..2] of byte;
  1460.     messagelength : byte;
  1461.           message : array [1..58] of byte;
  1462.           end;
  1463.     count : integer;
  1464.  
  1465. begin
  1466.   With Requestbuffer do begin
  1467.      bufferlength[1] := 1;
  1468.      bufferlength[2] := 0;
  1469.      subfunction := 1;
  1470.      end;
  1471.   With replybuffer do begin
  1472.      bufferlength[1] := 59;
  1473.      bufferlength[2] := 0;
  1474.      messagelength := 0;
  1475.      end;
  1476.      for count := 1 to 58 do replybuffer.message[count] := $0;
  1477.  
  1478.   With Regs do begin
  1479.      Ah := $e1;
  1480.      Ds := Seg(requestbuffer);
  1481.      Si := Ofs(requestbuffer);
  1482.      Es := Seg(replybuffer);
  1483.      Di := Ofs(replybuffer);
  1484.      end;
  1485.   MSDOS(Regs);
  1486.   retcode := Regs.al;
  1487.   bmessage := '';
  1488.   count := 0;
  1489.   if replybuffer.messagelength > 58 then replybuffer.messagelength := 58;
  1490.   if replybuffer.messagelength > 0 then
  1491.      for count := 1 to replybuffer.messagelength do
  1492.      bmessage := bmessage + chr(replybuffer.message[count]);
  1493.   { retcode = 0 if no message,  1 if message was retreived }
  1494.   if length(bmessage) = 0 then retcode := 1 else retcode := 0;
  1495.   end;
  1496.  
  1497. procedure get_server_datetime(var _year,_month,_day,_hour,_min,_sec,_dow:integer);
  1498. var replybuffer : record
  1499.            year : byte;
  1500.           month : byte;
  1501.             day : byte;
  1502.            hour : byte;
  1503.          minute : byte;
  1504.          second : byte;
  1505.             dow : byte;
  1506.             end;
  1507.  
  1508. begin
  1509.   With Regs do begin
  1510.      Ah := $e7;
  1511.      Ds := Seg(replybuffer);
  1512.      Dx := Ofs(replybuffer);
  1513.      end;
  1514.   MSDOS(Regs);
  1515.   retcode := Regs.al;
  1516.   _year := replybuffer.year;
  1517.   _month := replybuffer.month;
  1518.   _day := replybuffer.day;
  1519.   _hour := replybuffer.hour;
  1520.   _min := replybuffer.minute;
  1521.   _sec := replybuffer.second;
  1522.   _dow := replybuffer.dow;
  1523. end;
  1524.  
  1525. procedure set_date_from_server;
  1526. var replybuffer : record
  1527.            year : byte;
  1528.           month : byte;
  1529.             day : byte;
  1530.            hour : byte;
  1531.          minute : byte;
  1532.          second : byte;
  1533.             dow : byte;
  1534.             end;
  1535.  
  1536. begin
  1537.   With Regs do begin
  1538.      Ah := $e7;
  1539.      Ds := Seg(replybuffer);
  1540.      Dx := Ofs(replybuffer);
  1541.      end;
  1542.   MSDOS(Regs);
  1543.   setdate(replybuffer.year+1900,replybuffer.month,replybuffer.day);
  1544. end;
  1545.  
  1546. procedure set_time_from_server;
  1547. var replybuffer : record
  1548.            year : byte;
  1549.           month : byte;
  1550.             day : byte;
  1551.            hour : byte;
  1552.          minute : byte;
  1553.          second : byte;
  1554.             dow : byte;
  1555.             end;
  1556.  
  1557. begin
  1558.   With Regs do begin
  1559.      Ah := $e7;
  1560.      Ds := Seg(replybuffer);
  1561.      Dx := Ofs(replybuffer);
  1562.      end;
  1563.   MSDOS(Regs);
  1564.   settime(replybuffer.hour,replybuffer.minute,replybuffer.second,0);
  1565. end;
  1566.  
  1567. procedure get_server_version(var _version : string);
  1568. var  count,x : integer;
  1569.  
  1570.        request_buffer : record
  1571.         buffer_length : integer;
  1572.           subfunction : byte;
  1573.           end;
  1574.  
  1575.          reply_buffer : record
  1576.         buffer_length : integer;
  1577.                 stuff : array [1..512] of byte;
  1578.                 end;
  1579.  
  1580.         strings : array [1..3] of string;
  1581. begin
  1582.   With Regs do begin
  1583.      Ah := $e3;
  1584.      Ds := Seg(request_buffer);
  1585.      Si := Ofs(request_buffer);
  1586.      Es := Seg(reply_buffer);
  1587.      Di := Ofs(reply_buffer);
  1588.      end;
  1589.   With request_buffer do
  1590.   begin
  1591.      buffer_length := 1;
  1592.      subfunction := $c9;
  1593.   end;
  1594.   With reply_buffer do
  1595.   begin
  1596.      buffer_length := 512;
  1597.      for count := 1 to 512 do stuff[count] := $00;
  1598.   end;
  1599.   MSDOS(Regs);
  1600.   for count := 1 to 3 do strings[count] := '';
  1601.   x := 1;
  1602.   With reply_buffer do
  1603.   begin
  1604.     for count := 1 to 256 do
  1605.     begin
  1606.      if stuff[count] <> $0 then
  1607.         begin
  1608.          if not ((stuff[count]=32) and (strings[x]='')) then strings[x] :=
  1609. strings[x] + chr(stuff[count]);
  1610.         end;
  1611.      if stuff[count] = $0 then if x <> 3 then x := x + 1;
  1612.     end;
  1613.   End; { end of with }
  1614.   _version := strings[2];
  1615. end;
  1616.  
  1617. procedure open_message_pipe(var _connection, retcode : integer);
  1618. var  request_buffer : record
  1619.       buffer_length : integer;
  1620.         subfunction : byte;
  1621.    connection_count : byte;
  1622.     connection_list : byte;
  1623.                 end;
  1624.  
  1625.       reply_buffer : record
  1626.      buffer_length : integer;
  1627.   connection_count : byte;
  1628.        result_list : byte;
  1629.                end;
  1630. begin
  1631.   With Regs do begin
  1632.      Ah := $e1;
  1633.      Ds := Seg(request_buffer);
  1634.      Si := Ofs(request_buffer);
  1635.      Es := Seg(reply_buffer);
  1636.      Di := Ofs(reply_buffer);
  1637.      end;
  1638.   With request_buffer do
  1639.   begin
  1640.      buffer_length := 3;
  1641.      subfunction := $06;
  1642.      connection_count := $01;
  1643.      connection_list := _connection;
  1644.   end;
  1645.   With reply_buffer do
  1646.   begin
  1647.      buffer_length := 2;
  1648.      connection_count := 0;
  1649.      result_list := 0;
  1650.   end;
  1651.   MSDOS(Regs);
  1652.   retcode := reply_buffer.result_list;
  1653. end;
  1654.  
  1655. procedure close_message_pipe(var _connection, retcode : integer);
  1656. var  request_buffer : record
  1657.       buffer_length : integer;
  1658.         subfunction : byte;
  1659.    connection_count : byte;
  1660.     connection_list : byte;
  1661.                 end;
  1662.  
  1663.       reply_buffer : record
  1664.      buffer_length : integer;
  1665.   connection_count : byte;
  1666.        result_list : byte;
  1667.                end;
  1668. begin
  1669.   With Regs do begin
  1670.      Ah := $e1;
  1671.      Ds := Seg(request_buffer);
  1672.      Si := Ofs(request_buffer);
  1673.      Es := Seg(reply_buffer);
  1674.      Di := Ofs(reply_buffer);
  1675.      end;
  1676.   With request_buffer do
  1677.   begin
  1678.      buffer_length := 3;
  1679.      subfunction := $07;
  1680.      connection_count := $01;
  1681.      connection_list := _connection;
  1682.   end;
  1683.   With reply_buffer do
  1684.   begin
  1685.      buffer_length := 2;
  1686.      connection_count := 0;
  1687.      result_list := 0;
  1688.   end;
  1689.   MSDOS(Regs);
  1690.   retcode := reply_buffer.result_list;
  1691. end;
  1692.  
  1693. procedure check_message_pipe(var _connection, retcode : integer);
  1694. var request_buffer : record
  1695.      buffer_length : integer;
  1696.        subfunction : byte;
  1697.   connection_count : byte;
  1698.    connection_list : byte;
  1699.                end;
  1700.  
  1701.       reply_buffer : record
  1702.      buffer_length : integer;
  1703.   connection_count : byte;
  1704.        result_list : byte;
  1705.                end;
  1706. begin
  1707.   With Regs do begin
  1708.      Ah := $e1;
  1709.      Ds := Seg(request_buffer);
  1710.      Si := Ofs(request_buffer);
  1711.      Es := Seg(reply_buffer);
  1712.      Di := Ofs(reply_buffer);
  1713.      end;
  1714.   With request_buffer do
  1715.   begin
  1716.      buffer_length := 3;
  1717.      subfunction := $08;
  1718.      connection_count := $01;
  1719.      connection_list := _connection;
  1720.   end;
  1721.   With reply_buffer do
  1722.   begin
  1723.      buffer_length := 2;
  1724.      connection_count := 0;
  1725.      result_list := 0;
  1726.   end;
  1727.   MSDOS(Regs);
  1728.   retcode := reply_buffer.result_list;
  1729. end;
  1730.  
  1731.  
  1732. procedure send_personal_message(var _connection : integer; var _message :
  1733. string; var retcode : integer);
  1734. var count : integer;
  1735.  
  1736.       request_buffer : record
  1737.        buffer_length : integer;
  1738.          subfunction : byte;
  1739.     connection_count : byte;
  1740.      connection_list : byte;
  1741.       message_length : byte;
  1742.              message : array [1..126] of byte;
  1743.                  end;
  1744.  
  1745.         reply_buffer : record
  1746.        buffer_length : integer;
  1747.     connection_count : byte;
  1748.          result_list : byte;
  1749.                  end;
  1750.  
  1751. begin
  1752.   With Regs do begin
  1753.      Ah := $e1;
  1754.      Ds := Seg(request_buffer);
  1755.      Si := Ofs(request_buffer);
  1756.      Es := Seg(reply_buffer);
  1757.      Di := Ofs(reply_buffer);
  1758.      end;
  1759.   With request_buffer do
  1760.   begin
  1761.      subfunction := $04;
  1762.      connection_count := $01;
  1763.      connection_list := _connection;
  1764.      message_length := length(_message);
  1765.      buffer_length := length(_message) + 4;
  1766.      for count := 1 to 126 do message[count] := $00;
  1767.      if message_length > 0 then for count := 1 to message_length do
  1768.         message[count] := ord(_message[count]);
  1769.   end;
  1770.   With reply_buffer do
  1771.   begin
  1772.      buffer_length := 2;
  1773.      connection_count := 0;
  1774.      result_list := 0;
  1775.   end;
  1776.   MSDOS(Regs);
  1777.   retcode := reply_buffer.result_list;
  1778. end;
  1779.  
  1780. procedure purge_erased_files(var retcode:integer);
  1781. var  request_buffer : record
  1782.       buffer_length : integer;
  1783.         subfunction : byte;
  1784.                 end;
  1785.  
  1786.        reply_buffer : record
  1787.       buffer_length : integer;
  1788.                 end;
  1789. begin
  1790.   With request_buffer do
  1791.     begin
  1792.     buffer_length := 1;
  1793.     subfunction := $10;
  1794.     end;
  1795.   With reply_buffer do buffer_length := 0;
  1796.   With Regs do begin
  1797.    Ah := $E2;
  1798.    Ds := Seg(request_buffer);
  1799.    Si := Ofs(request_buffer);
  1800.    Es := Seg(reply_buffer);
  1801.    Di := Ofs(reply_buffer);
  1802.    end;
  1803.   msdos(regs);
  1804.   retcode := regs.al;
  1805. end;
  1806.  
  1807. procedure purge_all_erased_files(var retcode:integer);
  1808. var  request_buffer : record
  1809.       buffer_length : integer;
  1810.         subfunction : byte;
  1811.                 end;
  1812.  
  1813.        reply_buffer : record
  1814.       buffer_length : integer;
  1815.                 end;
  1816. begin
  1817.   With request_buffer do
  1818.     begin
  1819.     buffer_length := 1;
  1820.     subfunction := $CE;
  1821.     end;
  1822.   With reply_buffer do buffer_length := 0;
  1823.   With Regs do begin
  1824.    Ah := $E3;
  1825.    Ds := Seg(request_buffer);
  1826.    Si := Ofs(request_buffer);
  1827.    Es := Seg(reply_buffer);
  1828.    Di := Ofs(reply_buffer);
  1829.    end;
  1830.   msdos(regs);
  1831.   retcode := regs.al;
  1832. end;
  1833.  
  1834.  
  1835. procedure get_personal_message(var _connection : integer; var _message :
  1836. string; var retcode : integer);
  1837. var count : integer;
  1838.  
  1839.       request_buffer : record
  1840.        buffer_length : integer;
  1841.          subfunction : byte;
  1842.                  end;
  1843.  
  1844.         reply_buffer : record
  1845.        buffer_length : integer;
  1846.    source_connection : byte;
  1847.       message_length : byte;
  1848.       message_buffer : array [1..126] of byte;
  1849.                  end;
  1850.  
  1851. begin
  1852.     With Regs do begin
  1853.      Ah := $e1;
  1854.      Ds := Seg(request_buffer);
  1855.      Si := Ofs(request_buffer);
  1856.      Es := Seg(reply_buffer);
  1857.      Di := Ofs(reply_buffer);
  1858.      end;
  1859.   With request_buffer do
  1860.   begin
  1861.      buffer_length := 1;
  1862.      subfunction := $05;
  1863.   end;
  1864.   With reply_buffer do
  1865.   begin
  1866.      buffer_length := 128;
  1867.      source_connection := 0;
  1868.      message_length := 0;
  1869.      for count := 1 to 126 do message_buffer[count] := $0;
  1870.   end;
  1871.   MSDOS(Regs);
  1872.   _connection := reply_buffer.source_connection;
  1873.   _message := '';
  1874.   retcode := reply_buffer.message_length;
  1875.   if retcode > 0 then for count := 1 to retcode do
  1876.      _message := _message + chr(reply_buffer.message_buffer[count]);
  1877. end;
  1878.  
  1879. procedure log_file(lock_directive:integer; log_filename: string;
  1880. log_timeout:integer; var retcode:integer);
  1881. begin
  1882.     With Regs do begin
  1883.      Ah := $eb;
  1884.      Ds := Seg(log_filename);
  1885.      Dx := Ofs(log_filename);
  1886.      BP := log_timeout;
  1887.      end;
  1888. msdos(regs);
  1889. retcode := regs.al;
  1890. end;
  1891.  
  1892. procedure release_file(log_filename: string; var retcode:integer);
  1893. begin
  1894.     With Regs do begin
  1895.      Ah := $ec;
  1896.      Ds := Seg(log_filename);
  1897.      Dx := Ofs(log_filename);
  1898.      end;
  1899. msdos(regs);
  1900. retcode := regs.al;
  1901. end;
  1902.  
  1903. procedure clear_file(log_filename: string; var retcode:integer);
  1904. begin
  1905.     With Regs do begin
  1906.      Ah := $ed;
  1907.      Ds := Seg(log_filename);
  1908.      Dx := Ofs(log_filename);
  1909.      end;
  1910. msdos(regs);
  1911. retcode := regs.al;
  1912. end;
  1913.  
  1914. procedure clear_file_set;
  1915. begin
  1916.  regs.Ah := $cf;
  1917.  msdos(regs);
  1918.  retcode := regs.al;
  1919. end;
  1920.  
  1921. procedure lock_file_set(lock_timeout:integer; var retcode:integer);
  1922. begin
  1923.  regs.ah := $CB;
  1924.  regs.bp := lock_timeout;
  1925.  msdos(regs);
  1926.  retcode := regs.al;
  1927. end;
  1928.  
  1929. procedure release_file_set;
  1930. begin
  1931.  regs.ah := $CD;
  1932.  msdos(regs);
  1933. end;
  1934.  
  1935. procedure open_semaphore( _name:string;
  1936.                           _initial_value:shortint;
  1937.                           var _open_count:integer;
  1938.                           var _handle:longint;
  1939.                           var retcode:integer);
  1940. var s_name : array [1..129] of byte;
  1941.     count : integer;
  1942.     semaphore_handle : array [1..2] of word;
  1943. begin
  1944.   if (_initial_value < 0) or (_initial_value > 127) then _initial_value := 0;
  1945.   for count := 1 to 129 do s_name[count] := $00; {zero buffer}
  1946.   if length(_name) > 127 then _name := copy(_name,1,127); {limit name length}
  1947.   if length(_name) > 0 then for count := 1 to length(_name) do s_name[count+1]
  1948. := ord(_name[count]);
  1949.   s_name[1] := length(_name);
  1950.   regs.ah := $C5;
  1951.   regs.al := $00;
  1952.   move(_initial_value, regs.cl, 1);
  1953.   regs.ds := seg(s_name);
  1954.   regs.dx := ofs(s_name);
  1955.   regs.es := 0;
  1956.   msdos(regs);
  1957.   retcode := regs.al;
  1958.   if retcode = 0 then _open_count := regs.bl else _open_count := 0;
  1959.   semaphore_handle[1]:=regs.cx;
  1960.   semaphore_handle[2]:=regs.dx;
  1961.   move(semaphore_handle,_handle,4);
  1962. end;
  1963.  
  1964. procedure close_semaphore(var _handle:longint; var retcode:integer);
  1965. var semaphore_handle : array [1..2] of word;
  1966. begin
  1967.  move(_handle,semaphore_handle,4);
  1968.  regs.ah := $C5;
  1969.  regs.al := $04;
  1970.  regs.ds := 0;
  1971.  regs.es := 0;
  1972.  regs.cx := semaphore_handle[1];
  1973.  regs.dx := semaphore_handle[2];
  1974.  msdos(regs);
  1975.  retcode := regs.al;  { 00h=successful   FFh=Invalid handle}
  1976. end;
  1977.  
  1978. procedure examine_semaphore(var _handle:longint; var _value:shortint; var
  1979. _count, retcode:integer);
  1980. var semaphore_handle : array [1..2] of word;
  1981. begin
  1982.     move(_handle,semaphore_handle,4);
  1983.     regs.ah := $C5;
  1984.     regs.al := $01;
  1985.     regs.ds := 0;
  1986.     regs.es := 0;
  1987.     regs.cx := semaphore_handle[1];
  1988.     regs.dx := semaphore_handle[2];
  1989.     msdos(regs);
  1990.     retcode := regs.al; {00h=successful FFh=invalid handle}
  1991.     move(regs.cx, _value, 1);
  1992.     _count := regs.dl;
  1993. end;
  1994.  
  1995. procedure signal_semaphore(var _handle:longint; var retcode:integer);
  1996. var semaphore_handle : array [1..2] of word;
  1997. begin
  1998.     move(_handle,semaphore_handle,4);
  1999.     regs.ah := $C5;
  2000.     regs.al := $03;
  2001.     regs.ds := 0;
  2002.     regs.es := 0;
  2003.     regs.cx := semaphore_handle[1];
  2004.     regs.dx := semaphore_handle[2];
  2005.     msdos(regs);
  2006.     retcode := regs.al;
  2007.     {00h=successful   01h=overflow value > 127   FFh=invalid handle}
  2008. end;
  2009.  
  2010. procedure wait_on_semaphore(var _handle:longint; _timeout:integer; var
  2011. retcode:integer);
  2012. var semaphore_handle : array [1..2] of word;
  2013. begin
  2014.     move(_handle,semaphore_handle,4);
  2015.     regs.ah := $C5;
  2016.     regs.al := $02;
  2017.     regs.ds := 0;
  2018.     regs.es := 0;
  2019.     regs.bp := _timeout; {units in 1/18 of second,   0 = no wait}
  2020.     regs.cx := semaphore_handle[1];
  2021.     regs.dx := semaphore_handle[2];
  2022.     msdos(regs);
  2023.     retcode := regs.al;
  2024.     {00h=successful   FEh=timeout failure   FFh=invalid handle}
  2025. end;
  2026.  
  2027. procedure clear_connection(connection_number : integer; var retcode :
  2028. integer);
  2029. var con_num : byte;
  2030.  
  2031.     request_buffer : record
  2032.             length : integer;
  2033.        subfunction : byte;
  2034.            con_num : byte;
  2035.                end;
  2036.  
  2037.       reply_buffer : record
  2038.             length : integer;
  2039.                end;
  2040.  
  2041. begin
  2042.   with request_buffer do begin
  2043.      length := 4;
  2044.      con_num := connection_number;
  2045.      subfunction := $D2;
  2046.      end;
  2047.   reply_buffer.length := 0;
  2048.   with regs do begin
  2049.      Ah := $e3;
  2050.      Ds := Seg(request_buffer);
  2051.      Si := Ofs(request_buffer);
  2052.      Es := Seg(reply_buffer);
  2053.      Di := Ofs(reply_buffer);
  2054.      end;
  2055.   msdos(regs);
  2056.   retcode := regs.al;
  2057. end;
  2058.  
  2059.  
  2060. procedure get_server_lan_driver_information(var _lan_board_number : integer;
  2061. { This will return info on what }           var _text1,_text2:string;
  2062. { type of network cards are being }         var _network_address : byte4;
  2063. { used in the server. }                     var _host_address : byte6;
  2064.                                             var _driver_installed,
  2065.                                                 _option_number,
  2066.                                                 _retcode : integer);
  2067.  
  2068. var      count : integer;
  2069.           text : array [1..3] of string;
  2070.             x1 : integer;
  2071.  
  2072.          request_buffer : record
  2073.                  length : integer;
  2074.             subfunction : byte;
  2075.               lan_board : byte;
  2076.                      end;
  2077.  
  2078.            reply_buffer : record
  2079.                  length : integer;
  2080.         network_address : byte4;
  2081.            host_address : byte6;
  2082.    lan_driver_installed : byte;
  2083.           option_number : byte;
  2084.      configuration_text : array [1..160] of byte;
  2085.                      end;
  2086. begin
  2087.  with request_buffer do begin
  2088.       length := 2;
  2089.       subfunction := $E3;
  2090.       lan_board := _lan_board_number; { 0 to 3 }
  2091.       end;
  2092.  with reply_buffer do begin
  2093.       length := 174;
  2094.       for count := 1 to 4 do network_address[count] := $0;
  2095.       for count := 1 to 6 do host_address[count] := $0;
  2096.       lan_driver_installed := 0;
  2097.       option_number := 0;
  2098.       for count := 1 to 160 do configuration_text[count] := $0;
  2099.       end;
  2100.   with regs do begin
  2101.      Ah := $E3;
  2102.      Ds := Seg(request_buffer);
  2103.      Si := Ofs(request_buffer);
  2104.      Es := Seg(reply_buffer);
  2105.      Di := Ofs(reply_buffer);
  2106.      end;
  2107.   msdos(regs);
  2108.   retcode := regs.al;
  2109.   _text1 := '';
  2110.   _text2 := '';
  2111.   if retcode <> 0 then exit;
  2112.   _driver_installed := reply_buffer.lan_driver_installed;
  2113.   if reply_buffer.lan_driver_installed = 0 then exit;
  2114.   {-- set some values ---}
  2115.   for count := 1 to 3 do text[count] := '';
  2116.   x1 := 1;
  2117.     with reply_buffer do begin
  2118.       _network_address := network_address;
  2119.       _host_address := host_address;
  2120.       _option_number := option_number;
  2121.       for count := 1 to 160 do
  2122.       begin
  2123.       if ((configuration_text[count] = 0) and (x1 <> 3)) then x1 := x1+1;
  2124.       if configuration_text[count] <> 0 then
  2125.          text[x1] := text[x1] + chr(configuration_text[count]);
  2126.       end;
  2127.     end;
  2128.   _text1 := text[1];
  2129.   _text2 := text[2];
  2130. end;
  2131.  
  2132. end. { end of unit novell }
  2133.